package com.fz.us.admin.dict.dao.impl;

import com.fz.us.admin.base.dao.impl.BaseDaoImpl;
import com.fz.us.admin.base.dao.jdbc.JdbcDao;
import com.fz.us.admin.dict.dao.DictItemDao;
import com.fz.us.admin.dict.dto.DictItemDto;
import com.fz.us.admin.dict.entity.DictItem;
import org.springframework.jdbc.core.RowMapper;
import org.springframework.stereotype.Repository;
import org.springframework.util.Assert;

import javax.annotation.Resource;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * Dao实现类 - 字典Item
 * ============================================================================
 * 版权所有 2016 。
 *
 * @author fallenpanda
 * @version 1.0 2016-07-21 。
 * ============================================================================
 */
@Repository
public class DictItemDaoImpl extends BaseDaoImpl<DictItem,String > implements DictItemDao {

    @Resource
    private JdbcDao jdbcDao;

    @SuppressWarnings("unchecked")
    @Override
    public List<DictItem> listSystem(String dictId) {
        Assert.hasText(dictId, "dict is required");
        String hql = "from "+DictItem.class.getName()+" model where model.dict.id = :dictId and model.ifSystem = 1 and ( model.state = 'Enable' or model.state = 'Disenable' ) order by model.sortNo asc ";
        return getSession().createQuery(hql).setParameter("dictId", dictId).list();
    }

    @Override
    public List<DictItemDto> listDefault(String dictId, String keyId) {
        Assert.hasText(dictId, "dictId is required");
        Assert.hasText(keyId, "keyId is required");
        String sql = "select item.*, setting.id as sId, setting.name as sName, setting.pinYinHead as sPinYinHead, setting.pinYin as sPinYin, setting.state as sState from sys_dictitem as item left join ( select * from sys_dictitemsetting where keyId = :keyId and ( state = 'Enable' or state = 'Disenable' ) ) as setting on item.id = setting.dictId where item.dict_id = :dictId and ( ( item.ifSystem = 1 and item.state = 'Enable' ) or ( item.ifSystem = 0 and item.keyId = :keyId and ( item.state = 'Enable' or item.state = 'Disenable' ) ) ) order by item.sortNo asc";
        Map<String, String> filter = new HashMap<String, String>();
        filter.put("dictId", dictId);
        filter.put("keyId", keyId);
        return jdbcDao.query(sql, filter,new RowMapper<DictItemDto>(){
            public DictItemDto mapRow(ResultSet resultSet, int rowNum) throws SQLException {
                return resultToEntity(resultSet, rowNum);
            }
        });
    }

    @Override
    public List<DictItemDto> listSelectableDefined(String dictId, String keyId) {
        Assert.hasText(dictId, "dictId is required");
        Assert.hasText(keyId, "keyId is required");
        String sql = "select item.*, setting.id as sId, setting.name as sName, setting.pinYinHead as sPinYinHead, setting.pinYin as sPinYin, setting.state as sState from sys_dictitem as item left join ( select * from sys_dictitemsetting where keyId = :keyId and ( state = 'Enable' or state = 'Disenable' ) ) as setting on item.id = setting.dictId where item.dict_Id = :dictId and ( ( item.ifSystem = 1 and item.ifSelectable = 0 and item.state = 'Enable' ) or ( item.ifSystem = 0 and item.keyId = :keyId and item.state = 'Enable' ) ) and ( setting.state is null or setting.state = 'Enable' ) order by item.sortNo asc ";
        Map<String, String> filter = new HashMap<String, String>();
        filter.put("dictId", dictId);
        filter.put("keyId", keyId);
        return jdbcDao.query(sql, filter,new RowMapper<DictItemDto>(){
            public DictItemDto mapRow(ResultSet resultSet, int rowNum) throws SQLException {
                return resultToEntity(resultSet, rowNum);
            }
        });
    }

    @Override
    public DictItem getByValue(String dictId, String value) {
        Assert.hasText(dictId, "dictId is required");
        Assert.hasText(value, "value is required");
        String hql = "from "+DictItem.class.getName()+" model where model.dict.id = :dictId and model.ifSystem = 1 and model.value = :value ";
        return (DictItem) getSession().createQuery(hql).setParameter("dictId", dictId).setParameter("value", value).uniqueResult();
    }

    @Override
    public DictItem getByValue(String dictId, String keyId, String value) {
        Assert.hasText(dictId, "dictId is required");
        Assert.hasText(keyId, "keyId is required");
        Assert.hasText(value, "value is required");
        String hql = "from "+DictItem.class.getName()+" model where model.dict.id = :dictId and ( model.ifSystem = 1 or ( model.ifSystem = 0 and model.keyId = :keyId ) ) and model.value = :value ";
        return (DictItem) getSession().createQuery(hql).setParameter("dictId", dictId).setParameter("value", value).uniqueResult();
    }

    @Override
    public int getMaxSortNo(String dictId, String keyId) {
        Assert.hasText(dictId, "dictId is required");
        Assert.hasText(keyId, "keyId is required");
        String hql = "select max(model.sortNo) from "+DictItem.class.getName()+" model where model.dict.id = :dictId and ( ( model.ifSystem = 1 and model.state = 'Enable' ) or ( model.ifSystem = 0 and model.keyId = :keyId and ( model.state = 'Enable' or model.state = 'Disenable' ) ) )";
        Integer maxSortNo = (Integer) getSession().createQuery(hql).setParameter("dictId", dictId).setParameter("keyId", keyId).uniqueResult();
        return maxSortNo == null ? 0 : maxSortNo;
    }

    private DictItemDto resultToEntity(ResultSet resultSet, int rowNum) throws SQLException {
        DictItemDto dictItem = new DictItemDto();
        dictItem.dictId = resultSet.getString("dict_id");

        dictItem.id = resultSet.getString("id");
        dictItem.ifSystem = resultSet.getInt("ifSystem");
        dictItem.keyId = resultSet.getString("keyId");
        dictItem.name = resultSet.getString("name");
        dictItem.pinYinHead = resultSet.getString("pinYinHead");
        dictItem.pinYin = resultSet.getString("pinYin");
        dictItem.value = resultSet.getString("value");
        dictItem.description = resultSet.getString("description");
        dictItem.ifKey = resultSet.getInt("ifKey");
        dictItem.ifSelectable = resultSet.getInt("ifSelectable");
        dictItem.sortNo = resultSet.getInt("sortNo");
        dictItem.state = resultSet.getString("state");

        dictItem.parentId = resultSet.getString("parent_id");

        dictItem.sId = resultSet.getString("sId");
        dictItem.sName = resultSet.getString("sName");
        dictItem.sPinYinHead = resultSet.getString("sPinYinHead");
        dictItem.sPinYin = resultSet.getString("sPinYin");
        dictItem.sState = resultSet.getString("sState");

        return dictItem;
    }

}
